package com.cyzy.homework.service.impl;

import com.cyzy.homework.dto.HomeworkSubmitDTO;
import com.cyzy.homework.entity.Homework;
import com.cyzy.homework.entity.HomeworkSubmit;
import com.cyzy.homework.repository.HomeworkRepository;
import com.cyzy.homework.repository.HomeworkSubmitRepository;
import com.cyzy.homework.service.HomeworkSubmitService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;

/**
 * 作业提交服务实现类
 */
@Service
@Transactional
public class HomeworkSubmitServiceImpl implements HomeworkSubmitService {
    
    @Autowired
    private HomeworkSubmitRepository homeworkSubmitRepository;
    
    @Autowired
    private HomeworkRepository homeworkRepository;
    
    @Override
    public HomeworkSubmitDTO submitHomework(Long homeworkId, String userId, String content, List<MultipartFile> files) {
        // 检查作业是否存在
        Optional<Homework> optionalHomework = homeworkRepository.findById(homeworkId);
        if (!optionalHomework.isPresent()) {
            throw new RuntimeException("作业不存在");
        }
        
        Homework homework = optionalHomework.get();
        
        // 检查作业是否已发布 - 数据库中没有status字段，暂时跳过检查
        // if (homework.getStatus() != 1) {
        //     throw new RuntimeException("作业未发布，无法提交");
        // }
        
        // 检查是否已过期（允许在截止日期当天提交）
        if (homework.getDeadline() != null && homework.getDeadline().isBefore(LocalDateTime.now())) {
            throw new RuntimeException("作业已过期，无法提交");
        }
        
        // 检查是否已提交
        Optional<HomeworkSubmit> existingSubmit = homeworkSubmitRepository.findByHomeworkIdAndUserId(homeworkId, userId);
        if (existingSubmit.isPresent()) {
            throw new RuntimeException("作业已提交，无法重复提交");
        }
        
        // 创建提交记录
        HomeworkSubmit submit = new HomeworkSubmit();
        submit.setHomeworkId(homeworkId);
        submit.setUserId(userId);
        submit.setContent(content);
        submit.setStatus(1); // 已提交状态
        submit.setSubmitTime(LocalDateTime.now());
        
        submit = homeworkSubmitRepository.save(submit);
        
        // TODO: 处理文件上传
        // 这里需要实现文件上传逻辑
        
        return convertToDTO(submit);
    }
    
    @Override
    public HomeworkSubmitDTO updateSubmit(Long id, String userId, String content, List<MultipartFile> files) {
        Optional<HomeworkSubmit> optionalSubmit = homeworkSubmitRepository.findById(id);
        if (!optionalSubmit.isPresent()) {
            throw new RuntimeException("提交记录不存在");
        }
        
        HomeworkSubmit submit = optionalSubmit.get();
        
        // 检查权限
        if (!submit.getUserId().equals(userId)) {
            throw new RuntimeException("无权限修改此提交");
        }
        
        // 检查作业是否已过期
        Optional<Homework> optionalHomework = homeworkRepository.findById(submit.getHomeworkId());
        if (optionalHomework.isPresent()) {
            Homework homework = optionalHomework.get();
            if (homework.getDeadline().isBefore(LocalDateTime.now())) {
                throw new RuntimeException("作业已过期，无法修改提交");
            }
        }
        
        submit.setContent(content);
        submit.setSubmitTime(LocalDateTime.now());
        
        submit = homeworkSubmitRepository.save(submit);
        
        // TODO: 处理文件更新
        // 这里需要实现文件更新逻辑
        
        return convertToDTO(submit);
    }
    
    @Override
    public void deleteSubmit(Long id, String userId) {
        Optional<HomeworkSubmit> optionalSubmit = homeworkSubmitRepository.findById(id);
        if (!optionalSubmit.isPresent()) {
            throw new RuntimeException("提交记录不存在");
        }
        
        HomeworkSubmit submit = optionalSubmit.get();
        
        // 检查权限
        if (!submit.getUserId().equals(userId)) {
            throw new RuntimeException("无权限删除此提交");
        }
        
        // 检查作业是否已过期
        Optional<Homework> optionalHomework = homeworkRepository.findById(submit.getHomeworkId());
        if (optionalHomework.isPresent()) {
            Homework homework = optionalHomework.get();
            if (homework.getDeadline().isBefore(LocalDateTime.now())) {
                throw new RuntimeException("作业已过期，无法删除提交");
            }
        }
        
        homeworkSubmitRepository.deleteById(id);
    }
    
    @Override
    @Transactional(readOnly = true)
    public HomeworkSubmitDTO getSubmitById(Long id) {
        Optional<HomeworkSubmit> optionalSubmit = homeworkSubmitRepository.findById(id);
        if (!optionalSubmit.isPresent()) {
            throw new RuntimeException("提交记录不存在");
        }
        
        return convertToDTO(optionalSubmit.get());
    }
    
    @Override
    @Transactional(readOnly = true)
    public HomeworkSubmitDTO getSubmitByHomeworkIdAndUserId(Long homeworkId, String userId) {
        Optional<HomeworkSubmit> optionalSubmit = homeworkSubmitRepository.findByHomeworkIdAndUserId(homeworkId, userId);
        if (!optionalSubmit.isPresent()) {
            return null;
        }
        
        return convertToDTO(optionalSubmit.get());
    }
    
    @Override
    @Transactional(readOnly = true)
    public Page<HomeworkSubmitDTO> getSubmitsByHomeworkId(Long homeworkId, Pageable pageable) {
        Page<HomeworkSubmit> submitPage = homeworkSubmitRepository.findByHomeworkIdOrderBySubmitTimeDesc(homeworkId, pageable);
        return submitPage.map(this::convertToDTO);
    }
    
    @Override
    @Transactional(readOnly = true)
    public Page<HomeworkSubmitDTO> getSubmitsByUserId(String userId, Pageable pageable) {
        Page<HomeworkSubmit> submitPage = homeworkSubmitRepository.findByUserIdOrderBySubmitTimeDesc(userId, pageable);
        return submitPage.map(this::convertToDTO);
    }
    
    @Override
    @Transactional(readOnly = true)
    public Page<HomeworkSubmitDTO> getSubmitsByHomeworkIdAndStatus(Long homeworkId, Integer status, Pageable pageable) {
        Page<HomeworkSubmit> submitPage = homeworkSubmitRepository.findByHomeworkIdAndStatusOrderBySubmitTimeDesc(homeworkId, status, pageable);
        return submitPage.map(this::convertToDTO);
    }
    
    @Override
    public HomeworkSubmitDTO gradeHomework(Long id, String graderId, Integer score, String comment) {
        Optional<HomeworkSubmit> optionalSubmit = homeworkSubmitRepository.findById(id);
        if (!optionalSubmit.isPresent()) {
            throw new RuntimeException("提交记录不存在");
        }
        
        HomeworkSubmit submit = optionalSubmit.get();
        // submit.setScore(score); // 数据库中没有score字段
        // submit.setComment(comment); // 数据库中没有comment字段
        submit.setStatus(2); // 已批改状态
        // submit.setGradeTime(LocalDateTime.now()); // 数据库中没有grade_time字段
        // submit.setGraderId(graderId); // 数据库中没有grader_id字段
        
        submit = homeworkSubmitRepository.save(submit);
        return convertToDTO(submit);
    }
    
    @Override
    public List<HomeworkSubmitDTO> batchGradeHomework(List<Long> ids, String graderId, Integer score, String comment) {
        List<HomeworkSubmit> submits = homeworkSubmitRepository.findAllById(ids);
        
        for (HomeworkSubmit submit : submits) {
            // submit.setScore(score); // 数据库中没有score字段
            // submit.setComment(comment); // 数据库中没有comment字段
            submit.setStatus(2); // 已批改状态
            // submit.setGradeTime(LocalDateTime.now()); // 数据库中没有grade_time字段
            // submit.setGraderId(graderId); // 数据库中没有grader_id字段
        }
        
        submits = homeworkSubmitRepository.saveAll(submits);
        return submits.stream().map(this::convertToDTO).collect(Collectors.toList());
    }
    
    @Override
    @Transactional(readOnly = true)
    public List<HomeworkSubmitDTO> getUnGradedSubmits(Long homeworkId) {
        List<HomeworkSubmit> submits = homeworkSubmitRepository.findUnGradedSubmits(homeworkId);
        return submits.stream().map(this::convertToDTO).collect(Collectors.toList());
    }
    
    @Override
    @Transactional(readOnly = true)
    public List<HomeworkSubmitDTO> getGradedSubmits(Long homeworkId) {
        List<HomeworkSubmit> submits = homeworkSubmitRepository.findGradedSubmits(homeworkId);
        return submits.stream().map(this::convertToDTO).collect(Collectors.toList());
    }
    
    @Override
    @Transactional(readOnly = true)
    public boolean hasStudentSubmitted(Long homeworkId, String userId) {
        return homeworkSubmitRepository.findByHomeworkIdAndUserId(homeworkId, userId).isPresent();
    }
    
    @Override
    @Transactional(readOnly = true)
    public Object getStudentSubmitStatistics(String userId) {
        long totalCount = homeworkSubmitRepository.countByUserId(userId);
        long submittedCount = homeworkSubmitRepository.countByUserIdAndStatus(userId, 1);
        long gradedCount = homeworkSubmitRepository.countByUserIdAndStatus(userId, 2);
        
        Map<String, Object> statistics = new HashMap<>();
        statistics.put("totalCount", totalCount);
        statistics.put("submittedCount", submittedCount);
        statistics.put("gradedCount", gradedCount);
        statistics.put("pendingCount", totalCount - submittedCount);
        
        return statistics;
    }
    
    @Override
    @Transactional(readOnly = true)
    public Object getHomeworkSubmitStatistics(Long homeworkId) {
        long totalCount = homeworkSubmitRepository.countByHomeworkId(homeworkId);
        long submittedCount = homeworkSubmitRepository.countByHomeworkIdAndStatus(homeworkId, 1);
        long gradedCount = homeworkSubmitRepository.countByHomeworkIdAndStatus(homeworkId, 2);
        
        Map<String, Object> statistics = new HashMap<>();
        statistics.put("totalCount", totalCount);
        statistics.put("submittedCount", submittedCount);
        statistics.put("gradedCount", gradedCount);
        statistics.put("pendingCount", totalCount - submittedCount);
        
        return statistics;
    }
    
    /**
     * 转换为DTO
     */
    private HomeworkSubmitDTO convertToDTO(HomeworkSubmit submit) {
        HomeworkSubmitDTO submitDTO = new HomeworkSubmitDTO();
        BeanUtils.copyProperties(submit, submitDTO);
        return submitDTO;
    }
}
